package com.futu.es.service.Impl;

import com.futu.es.domain.MangodbSpot;
import com.futu.es.service.MangodbService;
import org.bson.Document;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Example;
import org.springframework.data.domain.ExampleMatcher;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.aggregation.AggregationResults;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;

import org.springframework.stereotype.Service;

import org.springframework.data.mongodb.core.aggregation.Aggregation;


import java.util.List;

@Service
public class MangodbServiceImpl {



    @Autowired
    private MongoTemplate mongoTemplate;

    /**
     * 使用动态条件查询MongoDB
     * 可以根据需要组合不同的查询条件
     */
    public List<MangodbSpot> findByConditions(MangodbSpot condition) {
        // 创建查询条件
        Query query = new Query();

        // 动态添加条件
        if (condition.getUserId() != null) {
            query.addCriteria(Criteria.where("user_id").is(condition.getUserId()));
        }

        if (condition.getSpotId() != null) {
            query.addCriteria(Criteria.where("spot_id").is(condition.getSpotId()));
        }

        if (condition.getUsername() != null && !condition.getUsername().isEmpty()) {
            query.addCriteria(Criteria.where("username").regex(".*" + condition.getUsername() + ".*"));
        }

        if (condition.getName() != null && !condition.getName().isEmpty()) {
            query.addCriteria(Criteria.where("spot_name").regex(".*" + condition.getName() + ".*"));
        }

        if (condition.getRating() != null) {
            query.addCriteria(Criteria.where("rating").gte(condition.getRating()));
        }

        // 执行查询并返回结果
        return mongoTemplate.find(query, MangodbSpot.class);
    }

    /**
     * 使用Example方式查询
     * 简单条件查询的另一种方式
     */


    /**
     * 地理位置搜索 - 查找指定坐标附近的景点
     */
    public List<MangodbSpot> findNearLocation(double latitude, double longitude, double maxDistance) {
        Query query = new Query();

        // 使用$near查询，查找附近的点
        query.addCriteria(Criteria.where("latitude").gte(latitude - maxDistance).lte(latitude + maxDistance)
                .and("longitude").gte(longitude - maxDistance).lte(longitude + maxDistance));

        return mongoTemplate.find(query, MangodbSpot.class);
    }

    /**
     * 使用聚合管道进行复杂查询
     * 例如：按景点分组统计平均评分
     */
    public List<MangodbSpot> findTopRatedSpots(int limit) {
        Query query = new Query();
        query.addCriteria(Criteria.where("rating").exists(true));
        query.with(Sort.by(Sort.Direction.DESC, "rating"));
        query.limit(limit);

        return mongoTemplate.find(query, MangodbSpot.class);
    }


    //查询用户最多访问的景点
    public MangodbSpot findMostVisitedSpots(Long userId) {
        // 1. 先查找用户访问最多的景点ID
        Aggregation idAggregation = Aggregation.newAggregation(
                Aggregation.match(Criteria.where("user_id").is(userId)),
                Aggregation.group("spot_id").count().as("visitCount"),
                Aggregation.sort(Sort.Direction.DESC, "visitCount"),
                Aggregation.limit(1)
        );

        AggregationResults<Document> idResult = mongoTemplate.aggregate(
                idAggregation, "user_spot_visits", Document.class);

        if (idResult.getMappedResults().isEmpty()) {
            return null;
        }

        // 2. 获取景点ID
        Document doc = idResult.getMappedResults().get(0);
        Long spotId = doc.get("_id") instanceof Long ?
                (Long) doc.get("_id") :
                Long.valueOf(doc.get("_id").toString());

        // 3. 根据景点ID查询完整的景点信息
        Query query = new Query(Criteria.where("spot_id").is(spotId));
        query.limit(1);

        List<MangodbSpot> spots = mongoTemplate.find(query, MangodbSpot.class, "user_spot_visits");
        return spots.isEmpty() ? null : spots.get(0);
    }
}
